#include "MyWindow.h"
#include <iostream>

void MyWindow::windowSize()
{
	setMinimumSize(MyWindow::winWidth, MyWindow::winHeight);
	resize(MyWindow::winWidth, MyWindow::winHeight);
	setWindowTitle(tr("Multimedia ToolBox"));
}

MyWindow::MyWindow(QMainWindow *parent):QMainWindow(parent)
{
	imageO = new ImageObj();
	soundO = new SoundObj(true);

	ui.setupUi(this);

	windowSize();

	tabs = new TabBar();

	buildActions();
	buildMenus();
	uploadSettings();

	connect(tabs, SIGNAL(currentChanged(int)), this, SLOT(disableMenus(int)));

	setCentralWidget(tabs);
}

void MyWindow::contextMenuEvent(QContextMenuEvent *event)
{
}


void MyWindow::uploadSettings()
{
	QFile settingsFile("conf.ini");

	if (!settingsFile.exists()) Settings::defaultSettings();
	else if (settingsFile.open(QIODevice::ReadOnly))
	{
		QTextStream stream(&settingsFile);
		QString line, sty, lang;

		do
		{
			line = stream.readLine();

			if (line.startsWith("STY: "))
			{
				sty = line.mid(5);
			}
			else if (line.startsWith("LANG: "))
			{
				lang = line.mid(6);
			}
		} while (!line.isNull() && (!sty.isNull() || !lang.isNull()));

		settingsList = new QStringList();

		settingsList->insert(0, lang);
		settingsList->insert(1, sty);

		applySettings(settingsList);
	}
}

void MyWindow::buildActions()
{
	actionsOnFile();
	actionsOnEdit();
	actionsOnView();
	actionsOnSettings();
	actionsOnHelp();
}

void MyWindow::buildMenus()
{
	buildFileMenu();
	buildEditMenu();
	buildViewMenu();
	buildSettingsMenu();
	buildHelpMenu();
}

void MyWindow::actionsOnFile()
{
	actionOpenFile = new QAction(QIcon("../img/open_ic.png"), tr("Open"), this);
	actionOpenFile->setShortcut(tr("Ctrl+O"));
	actionOpenFile->setStatusTip(tr("Open an existing file"));
	connect(actionOpenFile, SIGNAL(triggered()), this, SLOT(openFile()));

	//NLE
	actionNewFile = new QAction(QIcon("../img/open_ic.png"), tr("New sound"), this);
	actionNewFile->setShortcut(tr("Ctrl+N"));
	actionNewFile->setStatusTip(tr("Create a new sound"));
	connect(actionNewFile, SIGNAL(triggered()), this, SLOT(newSound()));

	if (tabs->currentIndex() != TabBar::SoundIndex) actionNewFile->setEnabled(false);

	actionSaveFile = new QAction(QIcon("../img/save_ic.png"), tr("Save"), this);
	actionSaveFile->setShortcut(tr("Ctrl+S"));
	actionSaveFile->setStatusTip(tr("Save the document to disk"));
	connect(actionSaveFile, SIGNAL(triggered()), this, SLOT(saveFile()));

	actionExit = new QAction(tr("Exit"), this);
	actionExit->setShortcut(tr("Ctrl+Q"));
	actionExit->setStatusTip(tr("Exit the application"));
	connect(actionExit, SIGNAL(triggered()), this, SLOT(close()));
}

void MyWindow::actionsOnEdit()
{
	actionEditImageCrop   = new QAction(QIcon("../img/crop_ic.png"), tr("Crop"), this);

	actionEditSoundCombine     = new QAction(tr("Combine"), this);
	connect(actionEditSoundCombine, SIGNAL(triggered()), this, SLOT(combine()));

	actionEditSoundConcatenate = new QAction(tr("Concatenate"), this);
	actionEditSoundConcatenate->setShortcut(tr("Ctrl+C"));
	connect(actionEditSoundConcatenate, SIGNAL(triggered()), this, SLOT(concatenate()));

	actionEditSoundEqualize    = new QAction(QIcon("../img/equalizer_ic.png"), tr("Equalize"), this);
	actionEditSoundEqualize->setShortcut(tr("Ctrl+E"));
	connect(actionEditSoundEqualize, SIGNAL(triggered()), this, SLOT(openEqualizer()));
}

void MyWindow::actionsOnView()
{
	actionViewImageDCT = new QAction(tr("DCT Computation"), this);
	connect(actionViewImageDCT, SIGNAL(triggered()), this, SLOT(imageDCT()));

	actionViewSoundFFT = new QAction(tr("FFT Computation"), this);
	connect(actionViewSoundFFT, SIGNAL(triggered()), this, SLOT(soundFFT()));
}

void MyWindow::actionsOnSettings()
{
	settings = new QAction(tr("Settings..."), this);
	connect(settings, SIGNAL(triggered()), this, SLOT(openSettings()));
}

void MyWindow::actionsOnHelp()
{
	actionHelp = new QAction(tr("Help"), this);
	actionAbout = new QAction(tr("About"), this);

	connect(actionAbout, SIGNAL(triggered()), this, SLOT(about()));
}

void MyWindow::about()
{
	aboutWin = new About(this);
	aboutWin->showNormal();
}


void MyWindow::buildFileMenu()
{
	menuFile = menuBar()->addMenu(tr("File"));
	menuFile->addAction(actionOpenFile);
	menuFile->addAction(actionNewFile);
	menuFile->addAction(actionSaveFile);
	menuFile->addSeparator();
	menuFile->addAction(actionExit);
}

void MyWindow::buildEditMenu()
{
	menuEdit = menuBar()->addMenu(tr("Edit"));

	menuEditImage = menuEdit->addMenu(QIcon("../img/image_ic.png"), tr("Image"));
	menuEditImage->addAction(actionEditImageCrop);

	menuEditSound = menuEdit->addMenu(QIcon("../img/sound_ic.png"), tr("Sound"));
	menuEditSound->addAction(actionEditSoundCombine);
	menuEditSound->addAction(actionEditSoundConcatenate);
	menuEditSound->addAction(actionEditSoundEqualize);

	if (this->tabs->currentIndex() == TabBar::SoundIndex)
	{
		menuEditImage->setEnabled(false);
	}
	else if (this->tabs->currentIndex() == TabBar::ImageIndex)
	{
		menuEditSound->setEnabled(false);
	}
}

void MyWindow::buildViewMenu()
{
	menuView = menuBar()->addMenu(tr("View"));

	menuViewImage = menuView->addMenu(QIcon("../img/image_ic.png"), tr("Image"));
	menuViewImage->addAction(actionViewImageDCT);

	menuViewSound = menuView->addMenu(QIcon("../img/sound_ic.png"), tr("Sound"));
	menuViewSound->addAction(actionViewSoundFFT);

	if (this->tabs->currentIndex() == TabBar::SoundIndex)
	{
		menuViewImage->setEnabled(false);
	}
	else if (this->tabs->currentIndex() == TabBar::ImageIndex)
	{
		menuViewSound->setEnabled(false);
	}
}

void MyWindow::buildSettingsMenu()
{
	menuSettings = menuBar()->addMenu(tr("Settings"));

	menuSettings->addAction(settings);
}

void MyWindow::buildHelpMenu()
{
	menuHelp = menuBar()->addMenu(tr("Help"));
	menuHelp->addAction(actionHelp);
	menuHelp->addAction(actionAbout);
}

void MyWindow::openFile()
{

	if (this->tabs->currentIndex() == TabBar::SoundIndex)
	{
		QString file = QFileDialog::getOpenFileName(this, tr("Open a File"), QDir::currentPath(), tr("Sound (*.wav)"));
		sound = new QSound(file);
		tabs->sendSound(sound);

		try
		{
			soundO = new SoundObj((file.toStdString()).c_str());
			tabs->sendSoundObj(soundO);
			tabs->getSoundTab()->buildBlocks();
			actionEditSoundEqualize->setEnabled(true);
		}
		catch(int code)
		{
			if (code == 0)
			{
				QMessageBox::critical(this, tr("Damaged file!"), tr("Error while opening this file") + file + " !");
			}
			else if (code == 2)
			{
				QMessageBox::warning(this, tr("Error!"), tr("This is not a PCM format :") + file + " !");
			}
		}
	}
	else if (this->tabs->currentIndex() == TabBar::ImageIndex)
	{
		QString file = QFileDialog::getOpenFileName(this, tr("Open a File"), QDir::currentPath(), tr("Image (*.bmp)"));
		if(file != "")
		{
			try
			{
				imageO = new ImageObj();
				imageO->openImage((file.toStdString()).c_str());
				tabs->paintImage(&imageO);
			}
			catch(int code)
			{
				if (code == 0)
				{
					QMessageBox::critical(this, tr("Format incorrect!"), tr("Le format du fichier n'est pas du BMP"));
				}
				if (code == 1)
				{
					QMessageBox::critical(this, tr("Erreur d'ouverture!"), tr("Impossible d'ouvrir le fichier"));
				}
				if (code == 2)
				{
					QMessageBox::critical(this, tr("Fichier est compress�!"), tr("Impossible d'ouvrir un fichier compr�ss�"));
				}
				if (code == 3)
				{
					QMessageBox::critical(this, tr("Fichier non conforme!"), tr("Impossible d'ouvrir un fichier BMP inf�rieur � 24 bits"));
				}

			}

		}
	}
}

void MyWindow::newSound()
{
		newSoundWin = new MyNewSoundWin(tabs->getSoundTab(), this, &soundO);//NLE2
		newSoundWin->showNormal();
}

bool MyWindow::saveFile()
{
	if (this->tabs->currentIndex() == TabBar::SoundIndex)
	{
		if (!soundO->getNbrOfChannels())
		{
			QMessageBox::warning(this, tr("Attention!"), tr("No sound to save"));
			return false;
		}
		else
		{
			QString file = QFileDialog::getSaveFileName(this,tr("Save a Sound"),QDir::currentPath(), tr("Sound (*.wav)"));
			soundO->Write((file.toStdString()).c_str());
			return true;
		}
	}
	else if (this->tabs->currentIndex() == TabBar::ImageIndex)
	{
		QString file = QFileDialog::getSaveFileName(this, tr("Save File"), QDir::currentPath(), tr("Image (*.BMP)"));
		imageO->writeImage((file.toStdString()).c_str());
		return true;
	}
}

void MyWindow::frenchLanguage()
{
	this->toolboxTranslator.load("../Multimedia_Toolbox_fr");
	a->installTranslator(&(this->toolboxTranslator));
	menuBar()->clear();
	buildActions();
	buildMenus();
	tabs -> repaint();
}

void MyWindow::englishLanguage()
{
	this->toolboxTranslator.load("../Multimedia_Toolbox_en");
	a->installTranslator(&(this->toolboxTranslator));
	menuBar()->clear();
	buildActions();
	buildMenus();
	tabs -> repaint();
}

void MyWindow::openSettings()
{
	settingsWin = new Settings(settingsList, this, this);
	settingsWin->showNormal();
}

void MyWindow::openEqualizer()
{
	equalizerWin = new EqualizeWindow(this->soundO, this);
	equalizerWin->showNormal();
}

void MyWindow::disableMenus(int id)
{
	if (id == TabBar::SoundIndex)
	{
		menuEditSound->setEnabled(true);
		menuEditImage->setEnabled(false);
		menuViewSound->setEnabled(true);
		menuViewImage->setEnabled(false);
		actionNewFile->setEnabled(true);
	}
	else if (id == TabBar::ImageIndex)
	{
		menuEditSound->setEnabled(false);
		menuEditImage->setEnabled(true);
		menuViewSound->setEnabled(false);
		menuViewImage->setEnabled(true);
		actionNewFile->setEnabled(false);
	}
}

void MyWindow::imageDCT()
{
	imageO->image = imageO->compositeDCT();
	tabs->paintImage(&imageO);
}

void MyWindow::soundFFT()
{
	if (this->soundO->getNbrOfChannels())
	{
		FFTPlot ** fft = new FFTPlot * [soundO->getNbrOfChannels()];

		for (long i=1; i<=soundO->getNbrOfChannels(); i++)
		{
			fft[i] = new FFTPlot(soundO, i);
			fft[i]->resize(200, 200);
			fft[i]->show();
		}
	}
	else
	{
		QMessageBox::warning(this, tr("Attention!"), tr("No opened sound"));
	}
}

void MyWindow::applySettings(QStringList * settingsList)
{
	if (settingsList->at(0).compare("FR") == 0) frenchLanguage();
	else if (settingsList->at(0).compare("EN") == 0) englishLanguage();
	else
	{
		settingsList->removeAt(0);
		settingsList->insert(0, "EN");
		englishLanguage();
	}

	if (!QStyleFactory::keys().contains(settingsList->at(1)))
	{
		settingsList->removeAt(1);
		settingsList->insert(1, "Plastique");
	}

	QStyle *style = QStyleFactory::create(settingsList->at(1));

	Q_ASSERT(style);

	QApplication::setStyle(style);
}

void MyWindow::concatenate()
{
	QString file = QFileDialog::getOpenFileName(this, tr("Concatenate with..."), QDir::currentPath(), tr("Sound (*.wav)"));

	try
	{
		this->soundO = (this->soundO)->Concat(new SoundObj((file.toStdString()).c_str()));

		tabs->sendSoundObj(soundO);
		tabs->getSoundTab()->buildBlocks();

	}
	catch(int code)
	{
		switch (code)
		{
		case 0:
			QMessageBox::critical(this, tr("Damaged file!"), tr("Error while opening this file") + file + " !");
			break;
		case 2:
			QMessageBox::warning(this, tr("Error!"), tr("This is not a PCM format :") + file + " !");
			break;
		case 4:
			QMessageBox::warning(this, tr("Error!"), tr("Files not on the same frequency : ") + file + " !");
			break;
		}
	}
}

void MyWindow::combine()
{
	QString file = QFileDialog::getOpenFileName(this, tr("Combine with..."), QDir::currentPath(), tr("Sound (*.wav)"));

	try
	{
		this->soundO->mixWith(new SoundObj((file.toStdString()).c_str()),2);

		tabs->sendSoundObj(soundO);
		tabs->getSoundTab()->buildBlocks();
	}

	catch(int code)
	{
		switch (code)
		{
		case -3:
		QMessageBox::critical(this, tr("Error!"), tr("Files don't have the same number of channels") + file + " !");
		break;
		case -2:
		QMessageBox::warning(this, tr("Error!"), tr("Files not on the same sample size :") + file + " !");
		break;
		case -1:
		QMessageBox::warning(this, tr("Error!"), tr("Files not on the same frequency : ") + file + " !");
		break;
		}
	}

}

MyWindow::~MyWindow(){}
